﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using SurfaceAd.Assistant;
using SurfaceAd.Common;
using SurfaceAd.Entities;
using SurfaceAd.Entities.Ad;
using Windows.UI;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using Windows.UI.Xaml.Controls.Primitives;
using Windows.UI.Xaml.Media;

/**
 * 创建时间：2014/10/10 10:27:05
 * 作者：yong.blackcore
 * Email：itblackhole@outlook.com
 * QQ：50404503
 */
namespace SurfaceAd.Views
{
    internal sealed class VideoPage
    {
        public event EventHandler OnCloseIconHandler, OnOpenAdContentScreenHandler;
        public event AdVideoContentHandler OnAdVideoClick;

        private Popup popup;
        private Grid gridMain;
        private MediaElement mediaElement;
        private StackPanel spProgressInfo;
        private AdResponse adContent;
        private Image adCloseIcon, adVolumeIcon;
        private String IMAGE_CLOSE = "ms-appx:///SurfaceAdImages/close.png";
        private String IMAGE_NoSilence = "ms-appx:///SurfaceAdImages/nosilence.png", IMAGE_Silence = "ms-appx:///SurfaceAdImages/silence.png";
        private Slider slider;
        private TextBlock txtCurrentTimeSpan, txtTotalTimeSpan;
        private WebViewPage navigatePopup;

        public VideoPage()
        {
            if (popup == null)
            {
                popup = new Popup();
            }
            OrientationScreenSize screenSize = OrientationScreenSizeHelper.GetScreenSize();
            popup.Height = screenSize.Height;
            popup.Width = screenSize.Width;
        }

        public VideoPage(AdResponse adContent)
            : this()
        {
            this.adContent = adContent;
            //
            this.gridMain = new Grid() { VerticalAlignment = VerticalAlignment.Center, HorizontalAlignment = HorizontalAlignment.Center, Background = new SolidColorBrush(Colors.Red) };
            this.gridMain.Height = this.popup.Height;
            this.gridMain.Width = this.popup.Width;
            this.gridMain.RowDefinitions.Add(new RowDefinition() { Height = new GridLength(60) });
            this.gridMain.RowDefinitions.Add(new RowDefinition() { Height = new GridLength(10, GridUnitType.Star) });
            this.gridMain.RowDefinitions.Add(new RowDefinition() { Height = new GridLength(60) });
            this.gridMain.ColumnDefinitions.Add(new ColumnDefinition() { Width = new GridLength(60) });
            this.gridMain.ColumnDefinitions.Add(new ColumnDefinition() { Width = new GridLength(10, GridUnitType.Star) });
            this.gridMain.ColumnDefinitions.Add(new ColumnDefinition() { Width = new GridLength(60) });
            this.gridMain.ColumnDefinitions.Add(new ColumnDefinition() { Width = new GridLength(60) });
            //
            this.mediaElement = new MediaElement();
            //this.mediaElement.Height = this.popup.Height;
            //this.mediaElement.Width = this.popup.Width;
            this.mediaElement.AutoPlay = true;
            //this.mediaElement.IsFullWindow = true;
            //this.mediaElement.AreTransportControlsEnabled = true;
            //
            this.mediaElement.Loaded += mediaElement_Loaded;
            this.mediaElement.MediaOpened += mediaElement_MediaOpened;
            this.mediaElement.MediaFailed += mediaElement_MediaFailed;
            this.mediaElement.MediaEnded += mediaElement_MediaEnded;
            //
            Grid.SetColumn(this.mediaElement, 0);
            Grid.SetRow(this.mediaElement, 0);
            Grid.SetColumnSpan(this.mediaElement, 4);
            Grid.SetRowSpan(this.mediaElement, 3);
            this.gridMain.Children.Add(this.mediaElement);
            this.DrawProgressInfoToVideoPage();
            //
            this.OpenVideoPage();
        }



        #region 绘制媒体播放控制图标按钮
        /// <summary>
        /// 绘制打开目标地址的进度信息
        /// </summary>
        void DrawProgressInfoToVideoPage()
        {
            this.spProgressInfo = new StackPanel() { Height = 80, Width = 80, Background = new SolidColorBrush(Colors.Transparent), Orientation = Orientation.Vertical };
            this.spProgressInfo.VerticalAlignment = Windows.UI.Xaml.VerticalAlignment.Center;
            this.spProgressInfo.HorizontalAlignment = Windows.UI.Xaml.HorizontalAlignment.Center;
            ProgressRing progressRing = new ProgressRing() { Height = 30, Width = 30, IsActive = true, Background = new SolidColorBrush(Colors.Transparent), Visibility = Windows.UI.Xaml.Visibility.Visible };
            progressRing.VerticalAlignment = Windows.UI.Xaml.VerticalAlignment.Center;
            progressRing.HorizontalAlignment = Windows.UI.Xaml.HorizontalAlignment.Center;
            TextBlock txtInfo = new TextBlock() { Text = "正在加载中", FontSize = 16 };
            this.spProgressInfo.Children.Add(progressRing);
            this.spProgressInfo.Children.Add(txtInfo);
            //
            Grid.SetColumn(this.spProgressInfo, 0);
            Grid.SetRow(this.spProgressInfo, 0);
            Grid.SetColumnSpan(this.spProgressInfo, 4);
            Grid.SetRowSpan(this.spProgressInfo, 3);
            this.gridMain.Children.Add(this.spProgressInfo);
        }

        /// <summary>
        /// 绘制关闭Popup的Icon
        /// </summary>
        void DrawCloseIconToVideoPage()
        {
            try
            {
                double repeateSize = 40;
                this.adCloseIcon = new Image() { Height = repeateSize, Width = repeateSize, Stretch = Stretch.Uniform, Margin = new Windows.UI.Xaml.Thickness(0, 10, 10, 0) };
                this.adCloseIcon.Source = new Windows.UI.Xaml.Media.Imaging.BitmapImage(new Uri(this.IMAGE_CLOSE));
                this.adCloseIcon.HorizontalAlignment = Windows.UI.Xaml.HorizontalAlignment.Right;
                this.adCloseIcon.VerticalAlignment = Windows.UI.Xaml.VerticalAlignment.Top;
                //关闭广告位事件
                this.adCloseIcon.Tapped += delegate(object sender, Windows.UI.Xaml.Input.TappedRoutedEventArgs e)
                {
                    try
                    {
                        this.CloseVideoPage();
                    }
                    catch
                    {
                        LogHelper.LogError("内容查看窗口被关闭！", this.GetType(), "DrawCloseIconToWebViewPage");
                    }
                };
                Grid.SetColumn(this.adCloseIcon, 3);
                Grid.SetRow(this.adCloseIcon, 0);
                this.gridMain.Children.Add(this.adCloseIcon);
            }
            catch (Exception err)
            {
                LogHelper.LogError(err.ToString(), this.GetType(), "DrawCloseIconToWebViewPage");
            }
        }

        /// <summary>
        /// 静音设置图标
        /// </summary>
        void DrawVolumeIconToVideoPage()
        {
            try
            {
                double repeateSize = 40;
                this.adVolumeIcon = new Image() { Height = repeateSize, Width = repeateSize, Stretch = Stretch.Uniform, Margin = new Windows.UI.Xaml.Thickness(0, 10, 10, 0) };
                this.adVolumeIcon.Source = new Windows.UI.Xaml.Media.Imaging.BitmapImage(new Uri(this.IMAGE_NoSilence));
                this.adVolumeIcon.Tag = this.IMAGE_NoSilence;
                this.adVolumeIcon.HorizontalAlignment = Windows.UI.Xaml.HorizontalAlignment.Right;
                this.adVolumeIcon.VerticalAlignment = Windows.UI.Xaml.VerticalAlignment.Top;
                //关闭广告位事件
                this.adVolumeIcon.Tapped += delegate(object sender, Windows.UI.Xaml.Input.TappedRoutedEventArgs e)
                {
                    try
                    {
                        Image img = sender as Image;
                        if (img != null && img.Tag != null)
                        {
                            if (this.IMAGE_NoSilence.Equals(Convert.ToString(img.Tag)))
                            {
                                img.Tag = this.IMAGE_Silence;
                                this.mediaElement.IsMuted = true;
                                this.adVolumeIcon.Source = new Windows.UI.Xaml.Media.Imaging.BitmapImage(new Uri(this.IMAGE_Silence));
                            }
                            else if (this.IMAGE_Silence.Equals(Convert.ToString(img.Tag)))
                            {
                                img.Tag = this.IMAGE_NoSilence;
                                this.mediaElement.IsMuted = false;
                                this.adVolumeIcon.Source = new Windows.UI.Xaml.Media.Imaging.BitmapImage(new Uri(this.IMAGE_NoSilence));
                            }
                        }
                    }
                    catch
                    {
                        LogHelper.LogError("调整音量失败！", this.GetType(), "DrawVolumeIconToVideoPage");
                    }
                };
                Grid.SetColumn(this.adVolumeIcon, 3);
                Grid.SetRow(this.adVolumeIcon, 2);
                this.gridMain.Children.Add(this.adVolumeIcon);
            }
            catch (Exception err)
            {
                LogHelper.LogError(err.ToString(), this.GetType(), "DrawVolumeIconToVideoPage");
            }
        }

        void DrawVideoPlayProgressToVideoPage()
        {
            this.slider = new Slider() { Margin = new Thickness(10, 20, 10, 0) };
            this.txtCurrentTimeSpan = new TextBlock() { VerticalAlignment = VerticalAlignment.Bottom, HorizontalAlignment = HorizontalAlignment.Left, Margin = new Thickness(10, 0, 0, 0) };
            this.txtTotalTimeSpan = new TextBlock() { VerticalAlignment = VerticalAlignment.Bottom, HorizontalAlignment = HorizontalAlignment.Right, Margin = new Thickness(0, 0, 10, 0) };
            //
            Grid.SetColumn(this.txtCurrentTimeSpan, 0);
            Grid.SetRow(this.txtCurrentTimeSpan, 2);
            Grid.SetColumn(this.slider, 0);
            Grid.SetRow(this.slider, 2);
            Grid.SetColumnSpan(this.slider, 3);
            Grid.SetColumn(this.txtTotalTimeSpan, 2);
            Grid.SetRow(this.txtTotalTimeSpan, 2);
            //
            this.gridMain.Children.Add(this.txtTotalTimeSpan);
            this.gridMain.Children.Add(this.slider);
            this.gridMain.Children.Add(this.txtCurrentTimeSpan);
            //
            this.slider.ValueChanged += delegate(object sender, RangeBaseValueChangedEventArgs e)
            {
                var ts = TimeSpan.FromMilliseconds(e.NewValue);
                this.mediaElement.Position = ts;
            };
        }
        #endregion 绘制媒体播放控制图标按钮

        void mediaElement_MediaEnded(object sender, Windows.UI.Xaml.RoutedEventArgs e)
        {
            this.mediaElement.Position = new TimeSpan(0);
            this.mediaElement.Play();
        }

        void mediaElement_MediaFailed(object sender, Windows.UI.Xaml.ExceptionRoutedEventArgs e)
        {
            this.CloseVideoPage();
        }

        void mediaElement_MediaOpened(object sender, Windows.UI.Xaml.RoutedEventArgs e)
        {
            try
            {
                this.spProgressInfo.Visibility = Windows.UI.Xaml.Visibility.Collapsed;
                this.DrawCloseIconToVideoPage();
                this.DrawVolumeIconToVideoPage();
                this.DrawVideoPlayProgressToVideoPage();

                if (this.OnOpenAdContentScreenHandler != null)
                {
                    this.OnOpenAdContentScreenHandler(null, new EventArgs());
                }
                //
                var ts = this.mediaElement.NaturalDuration.TimeSpan;
                this.txtTotalTimeSpan.Text = string.Format("{0:00}:{1:00}:{2:00}", ts.Hours, ts.Minutes, ts.Seconds);
                this.slider.Maximum = ts.TotalMilliseconds;
                //
                this.mediaElement.Tapped += mediaElement_Tapped;
            }
            catch (Exception err)
            {
                LogHelper.LogError(err.ToString(), this.GetType(), "mediaElement_MediaOpened");
            }
        }

        void mediaElement_Tapped(object sender, Windows.UI.Xaml.Input.TappedRoutedEventArgs e)
        {
            ClickAdHandlerFromMediaElement();
        }

        void mediaElement_Loaded(object sender, RoutedEventArgs e)
        {
            DispatcherTimer timer = new DispatcherTimer();
            timer.Interval = TimeSpan.FromMilliseconds(1000);
            timer.Tick += (ss, ee) =>
            {
                if (this.mediaElement != null && this.txtCurrentTimeSpan != null && this.slider != null)
                {
                    //显示当前视频进度  
                    var ts = this.mediaElement.Position;
                    this.txtCurrentTimeSpan.Text = string.Format("{0:00}:{1:00}:{2:00}", ts.Hours, ts.Minutes, ts.Seconds);
                    this.slider.Value = ts.TotalMilliseconds;
                }
            };
            timer.Start();
        }

        #region 点击视频跳转至目标地址
        void ClickAdHandlerFromMediaElement()
        {
            if (this.mediaElement.CanPause)
            {
                this.mediaElement.Pause();
            }
            switch (adContent.AdContentJumpType)
            {
                case AdJumpType.Browser:
                    this.navigatePopup = new WebViewPage(this.adContent);
                    this.navigatePopup.OnOpenAdContentScreenHandler += delegate(object sender, EventArgs e)
                    {
                        if (this.OnAdVideoClick != null)
                        {
                            this.OnAdVideoClick(new SurfaceAdEventArgs() { StatusCode = SurfaceAdStatus.AdContent_OpenScreen, Description = "点击视频进入目标网页！" });
                        }
                    };
                    this.navigatePopup.OnCloseIconHandler += navigatePopup_OnCloseIconHandler;
                    break;
                case AdJumpType.Market:
                    MarketplaceDetailTask(new AdResponseHelper().GetJumpData(adContent));
                    break;
                case AdJumpType.Call:
                    PhoneCallTask(new AdResponseHelper().GetJumpData(adContent));
                    break;
                default:
                    this.mediaElement.Play();
                    break;
            }
        }

        void navigatePopup_OnCloseIconHandler(object sender, EventArgs e)
        {
            if (this.navigatePopup != null)
            {
                this.navigatePopup.OnCloseIconHandler -= navigatePopup_OnCloseIconHandler;
                this.navigatePopup.CloseWebViewPage();
                this.navigatePopup = null;
            }
            if (this.OnAdVideoClick != null)
            {
                this.OnAdVideoClick(new SurfaceAdEventArgs() { StatusCode = SurfaceAdStatus.AdContent_CloseScreen, Description = "从目标网页返回至视频播放页！" });
            }
            //重新启动广告请求
            this.mediaElement.Play();
        }

        /// <summary>
        /// 打开应用市场
        /// </summary>
        /// <param name="appId"></param>
        async void MarketplaceDetailTask(string appId)
        {
            try
            {
                Uri uri = new Uri(string.Concat(Constants.LaunchMarketplaceDetailTask, appId));
                var success = await Windows.System.Launcher.LaunchUriAsync(uri);
                if (this.OnAdVideoClick != null)
                {
                    this.OnAdVideoClick(new SurfaceAdEventArgs() { StatusCode = SurfaceAdStatus.AdContent_OpenScreen, Description = string.Concat("点击视频进入官方应用商店", success ? "成功" : "失败", "！") });
                }                
            }
            catch (Exception err)
            {
                LogHelper.LogError(err.ToString(), this.GetType(), "MarketplaceDetailTask");
            }
        }

        /// <summary>
        /// 打开拔打电话启动器
        /// </summary>
        /// <param name="phoneNumber"></param>
        async void PhoneCallTask(string phoneNumber)
        {
            try
            {
                Uri uri = new Uri(string.Concat(Constants.LaunchPhoneCallTask, phoneNumber));
                var success = await Windows.System.Launcher.LaunchUriAsync(uri);
                if (this.OnAdVideoClick != null)
                {
                    this.OnAdVideoClick(new SurfaceAdEventArgs() { StatusCode = SurfaceAdStatus.AdContent_OpenScreen, Description = string.Concat("点击视频打开电话拔号器", success ? "成功" : "失败", "！") });
                }
                //TODO WPWRTC 打开后怎么样去重启调度器(执行了Unload事件没)？
            }
            catch (Exception err)
            {
                LogHelper.LogError(err.ToString(), this.GetType(), "PhoneCallTask");               
            }
        }
        #endregion 点击视频跳转至目标地址


        /// <summary>
        /// 屏幕方向变更时Popup及其子元素也要变更
        /// </summary>
        public void OrientationChanged()
        {
            if (popup != null)
            {
                OrientationScreenSize screenSize = OrientationScreenSizeHelper.GetScreenSize();
                popup.Height = screenSize.Height;
                popup.Width = screenSize.Width;
                //
                this.gridMain.Height = this.popup.Height;
                this.gridMain.Width = this.popup.Width;
            }
        }


        /// <summary>
        /// 必须先保证Popup正常显示
        /// </summary>
        private void OpenVideoPage()
        {
            try
            {
                if (this.popup != null)
                {
                    this.popup.Child = this.gridMain;
                    string destinationUrl = new AdResponseHelper().GetJumpData(this.adContent);
                    if (string.IsNullOrWhiteSpace(destinationUrl) || string.IsNullOrWhiteSpace(this.adContent.AdVideo.VideoUrl))
                    {
                        this.CloseVideoPage();
                        return;
                    }
                    LogHelper.LogInfo("DestinationURL:\t" + this.adContent.AdVideo.DestinationURL);
                    this.popup.IsOpen = true;
                    //http://img.surfacead.com/video/5a088b5d441a80fe2830bdb04f75068a.mp4
                    this.mediaElement.Source = new Uri(this.adContent.AdVideo.VideoUrl);
                }
            }
            catch (Exception err)
            {
                LogHelper.LogError(err.ToString(), this.GetType(), "OpenVideoPage");
            }
        }

        /// <summary>
        /// 如果有弹出框，则先关闭弹出框
        /// </summary>
        public void CloseVideoPage()
        {
            if (this.popup != null)
            {
                try
                {
                    if (this.navigatePopup != null)
                    {
                        this.navigatePopup.CloseWebViewPage();
                    }
                    else
                    {
                        this.popup.IsOpen = false;
                        this.popup.Child = null;
                        if (this.OnCloseIconHandler != null)
                        {
                            //在此事件中必须使用-=来移除OnCloseIconHandler事件，否则会有死循环
                            this.OnCloseIconHandler(null, new EventArgs());
                        }
                    }
                }
                catch (Exception err)
                {
                    LogHelper.LogError(err.ToString(), this.GetType(), "CloseVideoPage");
                }
            }
        }

    }
}

